import type { Router } from 'vue-router';

import { ElMessage } from 'element-plus';
import NProgress from 'nprogress';
import 'nprogress/nprogress.css';
import { getToken } from '@/utils/auth';
import { isHttp } from '@/utils/validate';
import { isRelogin } from '@/utils/request';
import { useUserStore } from '@/store/modules/user';
import useSettingsStore from '@/store/modules/settings';
import { usePermissionStore } from '@/store/modules/permission';
import { isPathMatch } from '@/utils/validate';
import { RoutesAlias } from '../routesAlias';

const whiteList: string[] = [RoutesAlias.Login, RoutesAlias.Register];
const isWhiteList = (path: string) => whiteList.some(pattern => isPathMatch(pattern, path));

/**
 * 路由全局前置守卫
 * 处理进度条、获取菜单列表、动态路由注册、404 检查、工作标签页及页面标题设置
 */
export function setupBeforeEachGuard(router: Router): void {
  router.beforeEach(async (to, from) => {
    let title: string = typeof to.meta.title === 'function' ? to.meta.title(to) : to.meta.title ?? '';
    useSettingsStore().setTitle(title);
    NProgress.start();

    if (isWhiteList(to.path)) {
      NProgress.done();
      return true; // 放行
    }

    if (getToken()) {
      const userStore = useUserStore();
      if (userStore.roles.length === 0) {
        isRelogin.show = true;
        try {
          await userStore.getInfo();
          isRelogin.show = false;

          const permissionStore = usePermissionStore();
          const accessRoutes = await permissionStore.generateRoutes();

          await accessRoutes.forEach(route => {
            if (!isHttp(route.path) && !router.hasRoute(route.name!)) {
              router.addRoute(route);
            }
          });

          // replace 在这里的作用是to未被正确注册，需要重新加载一次，才能匹配到路由
          return { ...to, replace: true };
        } catch (err: any) {
          isRelogin.show = false;
          await userStore.logOut();
          ElMessage.error(err.message || '获取用户信息失败');
          return { path: RoutesAlias.Login, query: { redirect: to.fullPath } };
        }
      } else {
        return true; // 已有角色，直接放行
      }
    } else {
      // 无 token，跳转登录
      const redirect = to.fullPath ? { path: RoutesAlias.Login, query: { redirect: to.fullPath } } : { path: RoutesAlias.Login };
      return redirect;
    }
  });

  // 全局后置钩子：关闭进度条
  router.afterEach(() => {
    NProgress.done();
  });
}